#ifndef CPP_AUTOPTR_H
#define CPP_AUTOPTR_H

#include <Global.h>
#include <vector>

template <typename T>
class AutoPtr {
   public:
    typedef std::pair<int, T*> RefCounterPair;
    typedef std::vector<RefCounterPair> RefCounterVector;

    AutoPtr(T* ptr = nullptr) : mPtr(ptr) {
        addRefCounter(mPtr);
    };

    AutoPtr(AutoPtr& autoPtr) {
        mPtr = autoPtr.mPtr;
        autoPtr.mPtr = nullptr;
    }

    ~AutoPtr() {
        removeRefCounter(mPtr);
    };

    //@methor 返回对象指针
    T* operator->() const {
        return this->mPtr;
    };

    //@methor 返回对象
    T& operator*() const {
        //类中的ptr已经被初始化为A
        return *(this->mPtr);
    };

    bool isNull() const { return mPtr == nullptr; }

   private:
    bool addRefCounter(T* ptr) {
        bool isAdd = false;
        typename RefCounterVector::iterator it;
        for (it = sRefVector.begin(); it != sRefVector.end(); ++it) {
            RefCounterPair counter = *it;
            if (counter.second == ptr) {
                ++counter.first;
                isAdd = true;
                cvte_log_info("counter:%d", (int)counter.first);
                break;
            }
        }
        if (!isAdd) {
            RefCounterPair counterPair(1, ptr);
            sRefVector.push_back(counterPair);
        }
        return isAdd;
    };

    bool removeRefCounter(T* ptr) {
        bool isRemove = false;
        typename RefCounterVector::iterator it;
        for (it = sRefVector.begin(); it != sRefVector.end(); ++it) {
            RefCounterPair counter = *it;
            if (counter.second == ptr) {
                if (counter.first > 0) {
                    --counter.first;
                }
                if (counter.first <= 0) {
                    delete counter.second;
                    counter.second = nullptr;
                    mPtr = nullptr;
                    cvte_log_info("free pointer");
                    sRefVector.erase(it);
                    isRemove = true;
                }
                cvte_log_info("counter:%d", (int)counter.first);
                break;
            }
        }
        return isRemove;
    };

   private:
    static RefCounterVector sRefVector;
    T* mPtr;
};

template <typename T>
typename AutoPtr<T>::RefCounterVector AutoPtr<T>::sRefVector;

#endif /* CPP_AUTOPTR_H */